package com.app.oral.controller

import com.app.oral.config.ApiResponse
import com.app.oral.dto.TeacherClassDto
import com.app.oral.dto.CreateClassRequest
import com.app.oral.service.ClassService
import com.app.oral.util.TeacherPermissionHelper
import jakarta.servlet.http.HttpServletRequest
import org.springframework.http.ResponseEntity
import org.springframework.web.bind.annotation.*
import io.swagger.v3.oas.annotations.Operation
import io.swagger.v3.oas.annotations.Parameter
import io.swagger.v3.oas.annotations.responses.ApiResponse as SwaggerApiResponse
import io.swagger.v3.oas.annotations.responses.ApiResponses
import io.swagger.v3.oas.annotations.security.SecurityRequirement
import io.swagger.v3.oas.annotations.tags.Tag
import jakarta.validation.Valid

@RestController
@RequestMapping("/api/v1/classes")
@Tag(name = "班级管理", description = "班级信息查询相关接口")
class ClassController(
    private val classService: ClassService,
    private val teacherPermissionHelper: TeacherPermissionHelper
) {

    @Operation(
        summary = "获取所有班级",
        description = "获取系统中所有班级的列表信息"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "200", description = "获取成功")
    ])
    @GetMapping
    fun getAllClasses(): ApiResponse<List<Map<String, Any>>> {
        return try {
            val classes = classService.getAllClasses()
            val classesData = classes.map { classInfo ->
                mapOf<String, Any>(
                    "id" to (classInfo.id ?: 0),
                    "className" to classInfo.className,
                    "grade" to classInfo.grade,
                    "studentCount" to classService.getClassStudentCount(classInfo.id ?: 0)
                )
            }
            ApiResponse.ok("获取班级列表成功", classesData)
        } catch (e: Exception) {
            ApiResponse.error("获取班级列表失败")
        }
    }

    @Operation(
        summary = "按年级获取班级",
        description = "根据指定年级获取班级列表"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "200", description = "获取成功")
    ])
    @GetMapping("/grade/{grade}")
    fun getClassesByGrade(
        @Parameter(description = "年级编号") @PathVariable grade: Int
    ): ApiResponse<List<Map<String, Any>>> {
        return try {
            val classes = classService.getClassesByGrade(grade)
            val classesData = classes.map { classInfo ->
                mapOf<String, Any>(
                    "id" to (classInfo.id ?: 0),
                    "className" to classInfo.className,
                    "grade" to classInfo.grade
                )
            }
            ApiResponse.ok("获取年级班级列表成功", classesData)
        } catch (e: Exception) {
            ApiResponse.error("获取年级班级列表失败")
        }
    }

    @Operation(
        summary = "获取班级详情",
        description = "根据班级ID获取具体班级信息"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "200", description = "获取成功"),
        SwaggerApiResponse(responseCode = "404", description = "班级不存在")
    ])
    @GetMapping("/{id}")
    fun getClassById(
        @Parameter(description = "班级ID") @PathVariable id: Long
    ): ApiResponse<Map<String, Any>?> {
        return try {
            val classInfo = classService.getClassById(id)
            if (classInfo != null) {
                val classData = mapOf<String, Any>(
                    "id" to (classInfo.id ?: 0),
                    "className" to classInfo.className,
                    "grade" to classInfo.grade
                )
                ApiResponse.ok("获取班级信息成功", classData)
            } else {
                ApiResponse.error("班级不存在")
            }
        } catch (e: Exception) {
            ApiResponse.error("获取班级信息失败")
        }
    }

    /**
     * 教师专用 - 获取管理的班级列表
     */
    @Operation(
        summary = "获取教师管理的班级",
        description = "教师查看自己管理的所有班级信息"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "200", description = "获取成功"),
        SwaggerApiResponse(responseCode = "403", description = "权限不足")
    ])
    @SecurityRequirement(name = "BearerAuth")
    @GetMapping("/teacher/my-classes")
    fun getTeacherClasses(
        request: HttpServletRequest
    ): ResponseEntity<ApiResponse<List<TeacherClassDto>>> {
        // 验证教师身份
        val teacher = teacherPermissionHelper.validateTeacher(request)
            ?: return ResponseEntity.status(403).body(
                ApiResponse.error("权限不足，只有教师可以访问")
            )

        return try {
            val teacherClassIds = teacher.getClassIdList()
            
            // 获取教师管理的班级信息
            val teacherClasses = teacherClassIds.mapNotNull { classId ->
                classService.getClassById(classId)?.let { classInfo ->
                    TeacherClassDto(
                        classId = classInfo.id ?: 0,
                        className = classInfo.className,
                        targetGrade = classInfo.grade,
                        studentCount = classService.getClassStudentCount(classId)
                    )
                }
            }

            ResponseEntity.ok(ApiResponse.ok("获取教师管理班级成功", teacherClasses))
        } catch (e: Exception) {
            ResponseEntity.internalServerError().body(
                ApiResponse.error("获取班级信息失败")
            )
        }
    }

    @Operation(
        summary = "创建新班级",
        description = "管理员创建新的班级，年级范围1-9年级"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "201", description = "创建成功"),
        SwaggerApiResponse(responseCode = "400", description = "参数错误"),
        SwaggerApiResponse(responseCode = "409", description = "班级已存在")
    ])
    @PostMapping
    fun createClass(
        @Valid @RequestBody request: CreateClassRequest
    ): ResponseEntity<ApiResponse<Map<String, Any>?>> {
        return try {
            if (request.grade < 1 || request.grade > 9) {
                return ResponseEntity.badRequest().body(
                    ApiResponse.error("年级必须在1-9年级范围内")
                )
            }
            
            if (request.className.isBlank()) {
                return ResponseEntity.badRequest().body(
                    ApiResponse.error("班级名称不能为空")
                )
            }

            if (classService.existsByGradeAndClassName(request.grade, request.className)) {
                return ResponseEntity.status(409).body(
                    ApiResponse.error("该年级下已存在同名班级")
                )
            }

            val createdClass = classService.createClass(request.grade, request.className)
            val classData = mapOf<String, Any>(
                "id" to (createdClass.id ?: 0),
                "className" to createdClass.className,
                "grade" to createdClass.grade
            )
            
            ResponseEntity.status(201).body(
                ApiResponse.ok("班级创建成功", classData)
            )
        } catch (e: Exception) {
            ResponseEntity.internalServerError().body(
                ApiResponse.error("班级创建失败: ${e.message}")
            )
        }
    }

    @Operation(
        summary = "删除班级",
        description = "管理员删除指定班级，删除前会检查是否有关联数据"
    )
    @ApiResponses(value = [
        SwaggerApiResponse(responseCode = "200", description = "删除成功"),
        SwaggerApiResponse(responseCode = "404", description = "班级不存在"),
        SwaggerApiResponse(responseCode = "409", description = "班级下仍有学生，无法删除")
    ])
    @DeleteMapping("/{id}")
    fun deleteClass(
        @Parameter(description = "班级ID") @PathVariable id: Long
    ): ResponseEntity<ApiResponse<Nothing>> {
        return try {
            val classInfo = classService.getClassById(id)
            if (classInfo == null) {
                return ResponseEntity.status(404).body(
                    ApiResponse.error("班级不存在")
                )
            }

            val studentCount = classService.getClassStudentCount(id)
            if (studentCount > 0) {
                return ResponseEntity.status(409).body(
                    ApiResponse.error("班级下仍有 $studentCount 名学生，无法删除")
                )
            }

            val success = classService.deleteClass(id)
            if (success) {
                ResponseEntity.ok(ApiResponse.ok<Nothing>("班级删除成功"))
            } else {
                ResponseEntity.internalServerError().body(
                    ApiResponse.error("班级删除失败")
                )
            }
        } catch (e: Exception) {
            ResponseEntity.internalServerError().body(
                ApiResponse.error("班级删除失败: ${e.message}")
            )
        }
    }
}